﻿// --------------------------------------------------------------------------------------------------------------------
// <copyright file="FiniteMagazine.cs" company="">
//   
// </copyright>
// <summary>
//   The finite magazine.
// </summary>
// --------------------------------------------------------------------------------------------------------------------

namespace RescueRaiders.Models
{
    using System.Collections.Generic;
    using System.Linq;

    using Microsoft.Xna.Framework;
    using Microsoft.Xna.Framework.Graphics;

    /// <summary>
    /// The finite magazine.
    /// </summary>
    internal class FiniteMagazine : InfiniteMagazine
    {
        /// <summary>
        /// The loaded.
        /// </summary>
        private readonly Queue<Ammo> loaded;

        /// <summary>
        /// The spent.
        /// </summary>
        private readonly HashSet<Ammo> spent;

        /// <summary>
        /// Initializes a new instance of the <see cref="FiniteMagazine"/> class.
        /// </summary>
        /// <param name="totalSize">
        /// The total size.
        /// </param>
        /// <param name="texture">
        /// The texture.
        /// </param>
        /// <param name="maxrange">
        /// The maxrange.
        /// </param>
        public FiniteMagazine(int totalSize, Texture2D texture, float maxrange)
            : base(texture, maxrange)
        {
            loaded = new Queue<Ammo>(totalSize);
            spent = new HashSet<Ammo>();
            for (var i = 0; i < totalSize; i++)
            {
                loaded.Enqueue(new Ammo(texture, maxrange));
            }
        }

        /// <summary>
        /// Gets a value indicating whether IsLoaded.
        /// </summary>
        private bool IsLoaded
        {
            get
            {
                return loaded.Count > 0;
            }
        }

        /// <summary>
        /// Gets a value indicating whether IsSpent.
        /// </summary>
        private bool IsSpent
        {
            get
            {
                return spent.Count > 0;
            }
        }

        /// <summary>
        /// The fire.
        /// </summary>
        /// <param name="position">
        /// The position.
        /// </param>
        /// <param name="direction">
        /// The direction.
        /// </param>
        /// <param name="rotation">
        /// The rotation.
        /// </param>
        /// <param name="soundEmitter">
        /// The sound emitter.
        /// </param>
        public override void Fire(Vector2 position, Vector2 direction, float rotation, Vector3 soundEmitter)
        {
            if (IsLoaded)
            {
                var ammo = loaded.Dequeue();
                ammo.Fire(position, direction, rotation, soundEmitter);
                Fired.Add(ammo);
            }
        }

        /// <summary>
        /// The reload.
        /// </summary>
        public void Reload()
        {
            if (IsSpent)
            {
                var ammo = spent.First();
                spent.Remove(ammo);
                loaded.Enqueue(ammo);
            }
        }
    }
}